﻿using Microsoft.VisualStudio.TestTools.UnitTesting;
using Moq;
using Sustainalytics.Controversies.BusinessLogic;
using Sustainalytics.Entities;
using System;
using System.Collections.Generic;
using System.Linq.Expressions;

namespace Sustainalytics.Accounts.BusinessLogic.Tests
{
    [TestClass]
    public class UserIpLoginManagerTest
    {
        private static IUserIpLoginManager _loginManager;

        private static Mock<IPlainBl<User>> _mockBlUser;
        private static Mock<IPlainBl<ClientUser>> _mockClientUser;

        [ClassInitialize]
   
        public static void InitClass(TestContext context, IUserIpLoginManager loginManager, Mock<IPlainBl<User>> mockBlUser, Mock<IPlainBl<ClientUser>> mockClientUser)
        {
            _mockBlUser = mockBlUser;
            _mockClientUser = mockClientUser;
            _loginManager = loginManager;
        }

        [TestMethod]
        public void GetFakeUserIp_Return_User_Is_Already_Put()
        {
            var idAccount = Guid.Parse("ec7c8d0a-0beb-4550-8a85-a8b965a46901");
            var accountName = "Test";
            var accountIp = "10.0.0.1";
            var idUser = Guid.Parse("d6e54ac2-4f47-4584-a458-7c9ce644fbd3");
            var inputAddedUser = new User()
            {
                AccountId = idAccount,
                Id = idUser,
                IsFakeIpUser = true
            };
            _mockBlUser.Setup(a => a.ReadAllWhere(It.IsAny<Expression<Func<User, bool>>>(), null, null))
                .Returns(new List<User>()
                {
                inputAddedUser
                });
            var data = _loginManager.GetFakeUserIp(idAccount, accountName, accountIp);
            Assert.AreSame(inputAddedUser, data);
            _mockBlUser.Verify(a => a.ReadAllWhere(It.IsAny<Expression<Func<User, bool>>>(), null, null));
        }

        [TestMethod]
        public void GetFakeUserIp_Return_User_User_Will_Be_Created()
        {
            var idAccount = Guid.Parse("ec7c8d0a-0beb-4550-8a85-a8b965a46909");
            var accountName = "Test";
            var accountIp = "10.0.0.1";
            _loginManager.GetFakeUserIp(idAccount, accountName, accountIp);
            _mockBlUser.Verify(a => 
                a.CreateOrUpdate(
                    It.Is<User>(
                        d => d.IsFakeIpUser && 
                        d.AccountId.GetValueOrDefault() == idAccount && 
                        d.Id != Guid.Empty && 
                        d.Account == accountName && 
                        d.Email == string.Format("{0}.IPlogin@{0}.com", accountName))));
        }

        [TestMethod]
        public void GetFakeUserIp_Return_User_Create_User_Password()
        {
            var idAccount = Guid.Parse("ec7c8d0a-0beb-4550-8a85-a8b965a46909");
            var accountName = "Test";
            var accountIp = "10.0.0.1";
            var data = _loginManager.GetFakeUserIp(idAccount, accountName, accountIp);
            _mockBlUser.Verify(a => 
                a.CreateOrUpdate(
                    It.Is<User>(
                        d => d.IsFakeIpUser && 
                        d.AccountId.GetValueOrDefault() == idAccount && 
                        d.Id != Guid.Empty && 
                        d.Account == accountName && 
                        d.Email == string.Format("{0}.IPlogin@{0}.com", accountName))));
            _mockClientUser.Verify(d => d.CreateOrUpdate(It.Is<ClientUser>(a => a.Id == data.Id && a.PasswordExpirationDate == DateTime.MaxValue && !string.IsNullOrEmpty(a.Password))));
        }

        [TestCleanup]
        public void TestCleanup()
        {
            _mockBlUser.ResetCalls();
            _mockClientUser.ResetCalls();
        }
    }
}
